package myLearnjdk.jdk.util.concurrent.testCompletableFuture;

import java.util.concurrent.CompletableFuture;
import java.util.concurrent.ExecutionException;
import java.util.function.BiConsumer;
import java.util.function.BiFunction;
import java.util.function.Function;

import org.apache.poi.ss.formula.functions.T;

/**
 * 
 * @author yangcheng  
 * @date 2020年7月20日  
 * @version V1.0
 */
public class TestCompletableFuture {
	public static void main(String[] args) {
		try {
//			testCompletableFuture();
//			testCompletableFutureSeri();
			testCompletableFutureANDCompose();
		} catch (InterruptedException | ExecutionException e) {
			e.printStackTrace();
		}
		
		
	}
	/**
	 * CompletableFuture.supplyAsync执行的方法可以有返回值，
	 * CompletableFuture.runAsync执行的内容不能有返回值
	 * 以上特性与线程池的execute和submit一个道理
	 * 
	 * @throws InterruptedException
	 * @throws ExecutionException
	 */
	public static void testCompletableFuture() throws InterruptedException, ExecutionException{
		CompletableFuture<String> completableFuture = CompletableFuture.supplyAsync(
				() -> "ni hao "
				);
		System.out.println(completableFuture.get());
	}
	
	/**
	 * CompletableFuture执行串行链路,可以使用的方法有：thenApply thenAccept thenRun thenCompose
	 * 
	 * a -> b -> c
	 * @throws InterruptedException
	 * @throws ExecutionException
	 */
	public static void testCompletableFutureSeri() throws InterruptedException, ExecutionException{
		CompletableFuture completableFuture = CompletableFuture.runAsync(
				() -> { System.out.println("执行a");}
				).thenRunAsync(() ->  { System.out.println("执行b"); } )
				.thenRunAsync(() ->  { System.out.println("执行c"); } );
	}
	
	/**
	 * 多任务and聚合关系
	 * a \
	 * 	  C
	 * b /
	 * 
	 * @throws InterruptedException
	 * @throws ExecutionException
	 */
	public static void testCompletableFutureANDCompose() throws InterruptedException, ExecutionException{
		CompletableFuture completableFuturea = CompletableFuture.supplyAsync(
				() -> "a " ).thenCombine(CompletableFuture.supplyAsync(() -> "b"),
						new BiFunction<String, String, String>(){

							@Override
							public String apply(String t, String u) {
								System.out.println(t+":"+u);
								return t+":"+u;
							}}).exceptionally(new Function<Throwable, String>() {
								/**
								 * 当执行过程中发生任何异常执行到当前方法
								 */
								@Override
								public String apply(Throwable t) {
									return null;
								}
							});
		
		/**
		 * 当联合与 执行完成之后执行当前方法中内容
		 */
		completableFuturea.whenCompleteAsync(new BiConsumer<String, Throwable>() {
			@Override
			public void accept(String t, Throwable u) {
				System.out.println(t);
				
			}
			
		});
	}

}
